package com.zty.tool;

import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang.StringUtils;

import javax.servlet.http.HttpServletRequest;
import java.net.InetAddress;
import java.net.UnknownHostException;
import java.util.Enumeration;
import java.util.HashMap;
import java.util.Map;

/**
 * Ip工具类
 *
 * @author: ChickenWing
 * @date: 2023/1/15
 */
@Slf4j
public class IpUtils {

    private static final String DEFAULT_IP = "127.0.0.1";

    private static final String UN_KNOWN = "unknown";

    private static final int IP_MAX_LENGTH = 15;

    private static final String SPLIT = ",";


    private static String getLocalIp() {
        try {
            InetAddress localHost = InetAddress.getLocalHost();
            String localIp = localHost.getHostAddress();
            log.info("com.zty.tool.IpUtils.getLocalIp:{}", localIp);
            return localIp;
        } catch (Exception e) {
            log.error("com.zty.tool.IpUtils.getLocalIp.error:{}", e.getMessage(), e);
            return DEFAULT_IP;
        }
    }

    public static String getIp(HttpServletRequest request) {
        String ipAddress = null;
        try {
            // 尝试从HTTP头信息"x-forwarded-for"中获取IP地址
            // 这个头信息通常由代理服务器添加，用于标识原始请求的IP地址
            ipAddress = request.getHeader("x-forwarded-for");

            // 检查获取到的IP地址是否为空，长度是否为0，或者是否为字符串"unknown"（忽略大小写）
            // 如果是以上任一情况，则认为没有有效地从"x-forwarded-for"头中获取到IP地址
            if (ipAddress == null || ipAddress.length() == 0 || "unknown".equalsIgnoreCase(ipAddress)) {
                // 尝试从HTTP头信息"Proxy-Client-IP"中获取IP地址
                ipAddress = request.getHeader("Proxy-Client-IP");
            }

            // 继续检查获取到的IP地址是否有效，逻辑同上
            if (ipAddress == null || ipAddress.length() == 0 || "unknown".equalsIgnoreCase(ipAddress)) {
                // 尝试从HTTP头信息"WL-Proxy-Client-IP"中获取IP地址
                // 这个头信息是由WebLogic服务器添加的
                ipAddress = request.getHeader("WL-Proxy-Client-IP");
            }

            // 如果到目前为止，仍未获取到有效的IP地址
            if (ipAddress == null || ipAddress.length() == 0 || "unknown".equalsIgnoreCase(ipAddress)) {
                // 获取请求的远程IP地址，这通常是直接连接服务器的客户端IP地址
                ipAddress = request.getRemoteAddr();

                // 如果远程IP地址是"127.0.0.1"，即本机地址
                if (ipAddress.equals("127.0.0.1")) {
                    // 尝试通过网络接口获取本机的IP地址
                    InetAddress inet = null;
                    try {
                        inet = InetAddress.getLocalHost();
                    } catch (UnknownHostException e) {
                        // 如果获取失败，则打印堆栈跟踪信息
                        e.printStackTrace();
                    }
                    // 获取并设置本机的IP地址
                    ipAddress = inet.getHostAddress();
                }
            }

            // 对于经过多个代理的情况，IP地址可能包含多个值，由逗号分隔
            // 只取第一个IP地址作为客户端的真实IP
            if (ipAddress != null && ipAddress.length() > 15) {
                // 如果IP地址字符串的长度大于15，说明可能包含多个IP地址
                if (ipAddress.indexOf(",") > 0) {
                    // 只取第一个IP地址
                    ipAddress = ipAddress.substring(0, ipAddress.indexOf(","));
                }
            }

        } catch (Exception e) {
            ipAddress = "";
        }
        return ipAddress;
    }

    /**
     * 获取全部请求头
     *
     * @param request
     * @return
     */
    public static Map<String, String> getAllRequestHeader(HttpServletRequest request) {
        Enumeration<String> headerNames = request.getHeaderNames();
        Map<String, String> map = new HashMap<>();
        while (headerNames.hasMoreElements()) {
            String key = (String) headerNames.nextElement();
            //根据名称获取请求头的值
            String value = request.getHeader(key);
            map.put(key, value);
        }

        return map;
    }

}